package com.chen.blue;

import lombok.extern.slf4j.Slf4j;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.InetSocketAddress;
import java.net.Socket;
import java.util.concurrent.TimeUnit;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

@Slf4j
public class MinioInit {
    // MinIO默认端口
    private static final int MINIO_PORT = 9000;
    // 启动脚本名称
    private static final String MINIO_START_SCRIPT = "D:\\minio\\minioStart.bat";
    // 启动超时时间（秒）
    private static final int STARTUP_TIMEOUT_SECONDS = 10;
    // 是否启用自动启动功能
    private static boolean autoStartEnabled = true;

    /**
     * 初始化MinIO服务
     */
    public static void initMinio() {
        if (!autoStartEnabled) {
            log.info("MinIO自动启动功能已禁用");
            return;
        }

        try {
            if (isMinioRunning()) {
                log.info("MinIO已在运行中");
            } else {
                log.info("MinIO未运行，尝试自动启动...");
                startMinioServer();
            }
        } catch (Exception e) {
            log.error("MinIO初始化失败: {}", e.getMessage(), e);
        }
    }

    /**
     * 检查MinIO是否正在运行（通过检查端口）
     */
    private static boolean isMinioRunning() throws IOException, InterruptedException {
        log.debug("检查MinIO是否正在运行，端口: {}", MINIO_PORT);

        // 首先尝试使用Socket连接检查端口
        try (Socket socket = new Socket()) {
            socket.connect(new InetSocketAddress("localhost", MINIO_PORT), 3000);
            log.debug("通过Socket连接确认MinIO正在运行，端口: {}", MINIO_PORT);
            return true;
        } catch (IOException e) {
            log.debug("Socket连接检查失败，尝试通过netstat检查端口: {}", e.getMessage());
        }

        // Windows系统使用netstat命令检查端口
        ProcessBuilder processBuilder = new ProcessBuilder("netstat", "-ano");
        processBuilder.redirectErrorStream(true);

        Process process = processBuilder.start();

        try (BufferedReader reader = new BufferedReader(new InputStreamReader(process.getInputStream()))) {
            String line;
            Pattern pattern = Pattern.compile(".*:(\\d+)\\s.*LISTENING\\s+(\\d+)");

            while ((line = reader.readLine()) != null) {
                Matcher matcher = pattern.matcher(line);
                if (matcher.matches()) {
                    int port = Integer.parseInt(matcher.group(1));
                    // 找到对应端口，说明服务正在运行
                    if (port == MINIO_PORT) {
                        log.debug("发现监听端口 {} 的进程", MINIO_PORT);
                        return true;
                    }
                }
            }

            int exitCode = process.waitFor();
            log.debug("端口检查完成，退出码: {}", exitCode);
            return false;
        } finally {
            process.destroyForcibly();
        }
    }

    /**
     * 启动MinIO服务器
     */
    private static void startMinioServer() throws IOException, InterruptedException {
        log.info("正在启动MinIO服务器，执行脚本: {}", MINIO_START_SCRIPT);

        ProcessBuilder processBuilder = new ProcessBuilder(MINIO_START_SCRIPT);
        processBuilder.redirectErrorStream(true);

        Process process = processBuilder.start();

        try {
            // 等待指定时间检查启动状态
            boolean finished = process.waitFor(STARTUP_TIMEOUT_SECONDS, TimeUnit.SECONDS);

            if (finished) {
                // 进程已结束，可能启动失败
                int exitCode = process.exitValue();
                if (exitCode != 0) {
                    String errorOutput = readProcessOutput(new BufferedReader(new InputStreamReader(process.getInputStream())));
                    log.warn("MinIO启动脚本完成但可能失败，退出码: {}, 输出: {}", exitCode, errorOutput);
                } else {
                    log.info("MinIO启动脚本执行完成");
                }
            } else {
                // 进程仍在运行，可能启动成功
                log.info("MinIO启动脚本已在运行，等待验证...");

                // 增加验证次数，提高验证准确性
                boolean minioStarted = false;
                for (int i = 0; i < 5; i++) {
                    Thread.sleep(3000);
                    if (isMinioRunning()) {
                        minioStarted = true;
                        break;
                    }
                    log.debug("第{}次验证MinIO是否启动", i + 1);
                }

                if (minioStarted) {
                    log.info("MinIO服务器启动成功");
                } else {
                    log.warn("MinIO启动验证失败，但进程仍在运行");
                }
            }
        } catch (InterruptedException e) {
            process.destroyForcibly();
            Thread.currentThread().interrupt();
            throw new RuntimeException("MinIO启动过程被中断", e);
        }
    }

    /**
     * 读取进程输出
     */
    private static String readProcessOutput(BufferedReader reader) throws IOException {
        StringBuilder output = new StringBuilder();
        String line;
        while ((line = reader.readLine()) != null) {
            output.append(line).append("\n");
        }
        return output.toString();
    }

    /**
     * 手动检查MinIO状态（供其他地方调用）
     */
    public static boolean checkMinioStatus() {
        try {
            return isMinioRunning();
        } catch (Exception e) {
            log.error("检查MinIO状态失败: {}", e.getMessage());
            return false;
        }
    }
}
